package com.yrline.pay.util.concurrent;

import java.util.Locale;
import java.util.concurrent.ThreadFactory;
import java.util.concurrent.atomic.AtomicInteger;


/**
 * code from netty
 * @author fanrui@c-platform.com
 * @version 1.0.0
 */
public class IncreaseNameThreadFactory implements ThreadFactory {

	private static final AtomicInteger poolId = new AtomicInteger();

	private final AtomicInteger nextId = new AtomicInteger();

	private final String prefix;

	private final boolean daemon;

	private final int priority;



	public IncreaseNameThreadFactory(Class<?> poolType) {
		this(poolType, false, Thread.NORM_PRIORITY);
	}

	public IncreaseNameThreadFactory(Class<?> poolType, boolean daemon, int priority) {
		this(toPoolName(poolType), daemon, priority);
	}

	private static String toPoolName(Class<?> poolType) {
		if (poolType == null) {
			throw new NullPointerException("poolType");
		}
		String poolName;
		Package pkg = poolType.getPackage();
		if (pkg != null) {
			poolName = poolType.getName().substring(pkg.getName().length() + 1);
		} else {
			poolName = poolType.getName();
		}

		switch (poolName.length()) {
			case 0:
				return "unknown";
			case 1:
				return poolName.toLowerCase(Locale.US);
			default:
				if (Character.isUpperCase(poolName.charAt(0)) && Character.isLowerCase(poolName.charAt(1))) {
					return Character.toLowerCase(poolName.charAt(0)) + poolName.substring(1);
				} else {
					return poolName;
				}
		}
	}

	public IncreaseNameThreadFactory(String poolName, boolean daemon, int priority) {
		if (poolName == null) {
			throw new NullPointerException("poolName");
		}
		if (priority < Thread.MIN_PRIORITY || priority > Thread.MAX_PRIORITY) {
			throw new IllegalArgumentException("priority: " + priority + " (expected: Thread.MIN_PRIORITY <= priority <= Thread.MAX_PRIORITY)");
		}

		prefix = poolName + '-' + poolId.incrementAndGet() + '-';
		this.daemon = daemon;
		this.priority = priority;
	}

	@Override
	public Thread newThread(Runnable r) {
		Thread t = new Thread(r, prefix + nextId.incrementAndGet());
		try {
			if (t.isDaemon()) {
				if (!daemon) {
					t.setDaemon(false);
				}
			} else {
				if (daemon) {
					t.setDaemon(true);
				}
			}

			if (t.getPriority() != priority) {
				t.setPriority(priority);
			}
		}
		catch (Exception ignored) {
			// Doesn't matter even if failed to set.
		}

		return t;
	}
}
